﻿using System.Collections;
using System.Collections.Generic;
using UnityEngine;

/// <summary>
/// 三件事：
/// 1. 移动
/// 2. 按照方向移动
/// 3. 播放动画
/// </summary>
public class AgentMovement : MonoBehaviour
{
    CharacterController controller;

    Animator animator;

    /// <summary>
    /// 旋转速度
    /// </summary>
    [SerializeField]
    public float rotationSpeed;
    /// <summary>
    /// 移动速度
    /// </summary>
    public float movementSpeed;
    /// <summary>
    /// 重力
    /// </summary>
    public float gravity;

    [SerializeField]
    /// <summary>
    /// 运动方向
    /// </summary>
    Vector3 movementVector = Vector3.zero;

    [SerializeField]
    /// <summary>
    /// 旋转角度
    /// </summary>
    private float desiredRotationAngle = 0;

    private float inputVerticelDirection = 0;
    
    /// <summary>
    /// 处理运动量
    /// </summary>
    /// <param name="input">纵横输入</param>
    public void HandleMovement(Vector2 input)
    {
        if (controller.isGrounded)
        {
            if (input.y != 0)
            {
                if (input.y > 0)
                {
                    inputVerticelDirection = Mathf.CeilToInt(input.y);
                    movementVector = input.y * transform.forward * movementSpeed;

                }
                else
                {
                    inputVerticelDirection = Mathf.FloorToInt(input.y);
                    movementVector = input.y * transform.forward * movementSpeed / 2;

                }
            }
            else
            {
                //原地
                movementVector = Vector3.zero;
                animator.SetFloat("MOVE_Vertical", 0);
            }
        }
    }

    public void HandleMovementDirection(Vector3 direction)
    {
        //forward 和 direction的夹角
        desiredRotationAngle = Vector3.Angle(transform.forward, direction);
        //叉积求得法线，判断左转还是右转
        var crossProduct = Vector3.Cross(transform.forward, direction).y;
        if (crossProduct < 0)
        {
            desiredRotationAngle *= -1;
        }
    }

    private void RotateAgent()
    {
        if (desiredRotationAngle > 10 || desiredRotationAngle<-10)
        {
            transform.Rotate(Vector3.up * desiredRotationAngle * rotationSpeed * Time.deltaTime);
        }
    }

    /// <summary>
    /// 设置动画
    /// </summary>
    /// <returns></returns>
    private float SetCorrectAnimation(float inputVerticelDirection)
    {
        float currentAnimationSpeed = animator.GetFloat("MOVE_Vertical");
        if (desiredRotationAngle > 10 || desiredRotationAngle < -10)
        {
            //确保旋转时候的动画
            if (Mathf.Abs( currentAnimationSpeed ) < 0.2f)
            {
                currentAnimationSpeed += inputVerticelDirection * Time.deltaTime * 2;
                currentAnimationSpeed = Mathf.Clamp(currentAnimationSpeed, -0.2f, 0.2f);
            }
            SetMovementFloat(currentAnimationSpeed);
        }
        else
        {
            if (currentAnimationSpeed < 1)
            {
                currentAnimationSpeed += inputVerticelDirection * Time.deltaTime * 2;
            }
            else
            {
                currentAnimationSpeed = 1;
            }
            SetMovementFloat(Mathf.Clamp(currentAnimationSpeed, -1, 1));
        }
        return Mathf.Abs(currentAnimationSpeed);
    }

    public void SetMovementFloat(float value)
    {
        animator.SetFloat("MOVE_Vertical", value);
    }

    private void Start()
    {
        controller = GetComponent<CharacterController>();
        animator = GetComponent<Animator>();
    }

    private void Update()
    {
        //玩家着地且在移动中才能转动视角
        if (controller.isGrounded)
        {
            if (movementVector.magnitude > 0)
            {
                var animationSpeedMultiplier = SetCorrectAnimation(inputVerticelDirection);
                RotateAgent();
                //移动 乘上动画速度
                movementVector *= animationSpeedMultiplier;
            }
        }

        //向前移动并施加重力
        movementVector.y -= gravity;
        //角色控制器推动移动
        controller.Move(movementVector * Time.deltaTime);
    }
}
